package com.example.java_gobang.game;

import com.example.java_gobang.model.MatchResponse;
import com.example.java_gobang.model.User;
import com.fasterxml.jackson.databind.ObjectMapper;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;
import org.springframework.web.socket.TextMessage;
import org.springframework.web.socket.WebSocketSession;

import java.io.IOException;
import java.util.LinkedList;
import java.util.Queue;

//用户的匹配队列，用于管理玩家的匹配功能
@Component
public class Match {

    private ObjectMapper objectMapper = new ObjectMapper();
    @Autowired
    private  OnlineUserManager onlineUserManager;

    @Autowired
    private RoomManager roomMannager;
    //此处用三个队列来匹配三个分段的玩家，低于 2000 为 normal ，2000 到 3000 为 middle，大于 3000 为 high

    private Queue<User> normalQueue = new LinkedList<>();
    private Queue<User> middleQueue = new LinkedList<>();
    private Queue<User> highQueue = new LinkedList<>();

    public void addUser (User user){
        if (user.getScore() < 2000) {
            synchronized (normalQueue) {
                normalQueue.offer(user);
                normalQueue.notify();
            }
            System.out.println("把玩家 " + user.getUsername() + " 加入到了 normalQueue 中!");
        } else if (user.getScore() >= 2000 && user.getScore() < 3000) {
            synchronized (middleQueue) {
                middleQueue.offer(user);
                middleQueue.notify();
            }
            System.out.println("把玩家 " + user.getUsername() + " 加入到了 highQueue 中!");
        } else {
            synchronized (highQueue) {
                highQueue.offer(user);
                highQueue.notify();
            }
            System.out.println("把玩家 " + user.getUsername() + " 加入到了 veryHighQueue 中!");
        }
    }

    public void removeUser(User user){
        if (user.getScore() < 2000) {
            synchronized (normalQueue) {
                normalQueue.remove(user);
            }
            System.out.println("把玩家 " + user.getUsername() + " 从 normalQueue 移除了!");
        } else if (user.getScore() >= 2000 && user.getScore() < 3000) {
            synchronized (middleQueue) {
                middleQueue.remove(user);
            }
            System.out.println("把玩家 " + user.getUsername() + " 从 highQueue 移除了!");
        } else {
            synchronized (highQueue) {
                highQueue.remove(user);
            }
            System.out.println("把玩家 " + user.getUsername() + " 从 veryHighQueue 移除了!");
        }
    }

    public void UserMatch(Queue<User> matchQueue) {
        synchronized (matchQueue){
            try {
                while (matchQueue.size() < 2) {
                    matchQueue.wait();
                }
                User user1 = matchQueue.poll();
                User user2 = matchQueue.poll();
                System.out.println("匹配出两个玩家: " + user1.getUsername() + ", " + user2.getUsername());

                WebSocketSession user1WebSocketSession = onlineUserManager.getWebSocketSessionByUserIdInGameHall(user1.getUserId());
                WebSocketSession user2WebSocketSession = onlineUserManager.getWebSocketSessionByUserIdInGameHall(user2.getUserId());

                if (user1WebSocketSession == null){
                    //说明用户1下线了，要把用户2重新放入队列中
                    matchQueue.offer(user2);
                    return;
                }

                if (user2WebSocketSession == null){
                    //说明用户2下线了，要把用户1重新放入队列中
                    matchQueue.offer(user1);
                    return;
                }

                if (user1WebSocketSession == user2WebSocketSession){
                    //如果两个会话一样，说明用户跟自己匹配，这是不合理的
                    matchQueue.offer(user1);
                    return;
                }

                Room room = new Room();
                //如果两个会话都不为空的话，就把两个用户都加入游戏对决中
                roomMannager.addTwoUserBattle(room,user1,user2);

                // 接着给玩家反馈信息: 你匹配到对手了
                MatchResponse response1 = new MatchResponse();
                response1.setOk(true);
                response1.setMessage("matchSuccess");
                String json1 = objectMapper.writeValueAsString(response1);
                user1WebSocketSession.sendMessage(new TextMessage(json1));

                MatchResponse response2 = new MatchResponse();
                response2.setOk(true);
                response2.setMessage("matchSuccess");
                String json2 = objectMapper.writeValueAsString(response2);
                user2WebSocketSession.sendMessage(new TextMessage(json2));

            } catch (InterruptedException | IOException e) {
                e.printStackTrace();
            }

        }

    }

    public Match() {
        // 创建三个线程, 分别针对这三个匹配队列, 进行操作.
        Thread t1 = new Thread() {
            @Override
            public void run() {
                // 扫描 normalQueue
                while (true) {
                    UserMatch(normalQueue);
                }
            }
        };
        t1.start();

        Thread t2 = new Thread(){
            @Override
            public void run() {
                while (true) {
                    UserMatch(middleQueue);
                }
            }
        };
        t2.start();

        Thread t3 = new Thread() {
            @Override
            public void run() {
                while (true) {
                    UserMatch(highQueue);
                }
            }
        };
        t3.start();
    }
}
